<template>
    <div style="padding: 20px;">
        <el-card shadow="always" :body-style="{ padding: '20px' }">
            <el-form ref="form" label-width="80px" :inline="true">
                <el-form-item label="角色搜索">
                    <el-input v-model="searchValue" placeholder="请输入角色名" clearable style="width:250px;" />
                </el-form-item>
                <el-form-item>
                    <el-button type="primary" @click="search">搜索</el-button>
                </el-form-item>
            </el-form>
        </el-card>
        <el-card shadow="always" :body-style="{ padding: '20px' }">
            <el-button type="primary" size="default" @click="AddRole">添加角色</el-button>
            <el-table border class="user-table" :data="roleList">
                <el-table-column label="#" type="index" width="120" align="center"></el-table-column>
                <el-table-column label="角色id" width="120" align="center" prop="id"></el-table-column>
                <el-table-column label="角色名称" width="240" align="center" prop="roleName"></el-table-column>
                <el-table-column label="创建时间" align="center" prop="createTime"></el-table-column>
                <el-table-column label="更新时间" align="center" prop="updateTime"></el-table-column>
                <el-table-column label="操作" width="320" align="center">
                    <template #default="scope">
                        <el-button type="primary" size="default" @click="AssignPermission(scope.row)">分配权限</el-button>
                        <el-button type="primary" size="default" @click="EditRole(scope.row)">编辑</el-button>
                        <el-popconfirm title="你确定要删除此角色吗？" @confirm="DeleteRole(scope.row.id)">
                            <template #reference>
                                <el-button type="danger" size="default">删除</el-button>
                            </template>
                        </el-popconfirm>
                    </template>
                </el-table-column>
            </el-table>
            <el-pagination v-model:current-page="PageNo" v-model:page-size="pageSize" :page-sizes="[5, 10, 20, 30]"
                :background="true" layout="  sizes,prev, pager, next, ->,jumper,total" :total="total" />
        </el-card>
        <!-- 添加和修改角色 -->
        <el-dialog v-model="dialogVisible" :title="roleParams.id ? '编辑角色' : '添加新角色'" width="500">
            <el-form :model="roleParams" ref="roleFormRef" :rules="rules" label-width="80px" :inline="false">
                <el-form-item label="角色名称" prop="roleName">
                    <el-input v-model="roleParams.roleName" placeholder="请输入角色名称" clearable />
                </el-form-item>
            </el-form>
            <template #footer>
                <el-button type="primary" @click="handleAddRole">确定</el-button>
                <el-button type="primary" @click="handleCancel">取消</el-button>
            </template>
        </el-dialog>
        <!-- 分配权限 -->
        <el-drawer v-model="drawer">
            <template #header>
                <h4>分配角色权限</h4>
            </template>
            <template #default>
                <el-tree ref="treeRef" :data="rolePermissionList" show-checkbox node-key="id" :props="defaultProps"
                    :default-checked-keys="checkedKeys"></el-tree>
            </template>
            <template #footer>
                <el-button type="primary" @click="handleassignPermission">确定</el-button>
                <el-button type="primary" @click="drawer = false">取消</el-button>
            </template>
        </el-drawer>
    </div>
</template>
<script setup lang="ts">
import { addorupdateRole, assignPermission, deleteRole, getAllPermissionList, getAllRoleList } from '@/api/acl/role';
import { nextTick, onMounted, ref, watch } from 'vue';
import type { RoleData } from '@/api/acl/user/type';
import { ElMessage } from 'element-plus';
import type { PermissionListData } from '@/api/acl/role/type';
import { useThrottle } from '@/utils/throttle';
let dialogVisible = ref(false)
let drawer = ref(false)
let treeRef = ref<any>(null)
let searchValue = ref('')
let PageNo = ref(1)
let pageSize = ref(5)
let total = ref(0)
let roleList = ref<RoleData[]>([])
let rolePermissionList = ref<PermissionListData[]>([])
let defaultProps = ref({
    children: 'children',
    label: 'name'
})
let roleParams = ref<RoleData>({
    id: 0,
    roleName: ''
})
let roleFormRef = ref<any>(null)
const search = () => {
    console.log(searchValue.value)
}
const getRoleListData = async () => {
    while (true) {
        const result = await getAllRoleList(PageNo.value, pageSize.value, searchValue.value)
        if (result.code === 200) {
            total.value = result.data.total
            roleList.value = result.data.records
            break
        }
    }
}
const AddRole = () => {
    dialogVisible.value = true
    nextTick(() => {
        clearRoleParams()
        roleFormRef.value.clearValidate()
    })
}
//获取该角色的权限列表
const AssignPermission = async (row: RoleData) => {
    while (true) {
        const result = await getAllPermissionList(row.id)
        if (result.code === 200) {
            rolePermissionList.value = result.data
            checkedKeys.value = []
            roleParams.value = row
            filterPermissionList(rolePermissionList.value)
            break
        }
        else if (result.code === 201) {
            ElMessage.error(result.message)
            break
        }
        else {
            console.log('获取权限列表失败,正在重试')
        }
    }
    drawer.value = true
}
const EditRole = (row: RoleData) => {
    dialogVisible.value = true
    nextTick(() => {
        roleParams.value = row
        roleFormRef.value.clearValidate()
    })
}
// 删除
const DeleteRole = useThrottle(async (roleId: number) => {
    let i = 0
    while (i++ < 5) {
        try {
            const res = await deleteRole(roleId)
            if (res.code === 200) {
                window.location.reload()
                break
            }
            else if (res.code === 201) {
                ElMessage.error(res.message)
                break
            }
        }
        catch (error) {
            console.log('删除失败,正在重试')
        }
    }
}, 1000)
// 添加
const handleAddRole = useThrottle(async () => {
    await roleFormRef.value.validate()
    while (true) {
        try {
            const res = await addorupdateRole(roleParams.value)
            if (res.code === 200) {
                dialogVisible.value = false
                getRoleListData()
                ElMessage.success(roleParams.value.id ? '编辑角色成功' : '添加角色成功')
                break
            }
            else if (res.code === 201) {
                ElMessage.error(res.message)
                break
            }
        }
        catch (error) {
            console.log('添加失败,正在重试')
        }
    }
}, 1000)
// 取消
const handleCancel = () => {
    dialogVisible.value = false
    clearRoleParams()
}
// 分配权限
const handleassignPermission = useThrottle(async () => {
    while (true) {
        const checkedKeysParam = checkedKeys.value.concat(treeRef.value.getHalfCheckedKeys())
        const res = await assignPermission(roleParams.value.id, checkedKeysParam)
        if (res.code === 200) {
            drawer.value = false
            clearRoleParams()
            window.location.reload()
            break
        }
        else if (res.code === 201) {
            ElMessage.error(res.message)
            break
        }
        else {
            console.log('分配权限失败,正在重试')
        }
    }
}, 1000)
const validateRoleName = (_rule: any, value: any, callback: any) => {
    if (value === '') {
        callback(new Error('请输入角色名称'))
    }
    else if (value.length < 2 || value.length > 10) {
        callback(new Error('角色名称长度在2-10个字符之间'))
    }
    else {
        callback()
    }
}
const rules = {
    roleName: [
        { required: true, trigger: 'blur', validator: validateRoleName }
    ]
}
const clearRoleParams = () => {
    roleParams.value = {
        id: 0,
        roleName: ''
    }
}
let checkedKeys = ref<number[]>([])
// 过滤权限列表
const filterPermissionList = (list: PermissionListData[]) => {
    const traverse = (nodes: PermissionListData[]) => {
        nodes.forEach((node) => {
            if (!node.children || node.children.length === 0) {
                if (node.select) {
                    checkedKeys.value.push(node.id);
                }
            } else {
                traverse(node.children);
            }
        });
    };
    traverse(list);
}
onMounted(() => {
    getRoleListData()
})
watch([PageNo, pageSize], () => {
    getRoleListData()
})
</script>
